import React, {useState, useEffect} from 'react';
import './App.css';


const getItemMsg = (id, list) => {
    let msgItem = {};
    list.map(item => {
        if (item.id === id) {
            msgItem = item
        }
    });
    list = null;
    msgItem.pid = id;
    return msgItem
}

const MoveItem = (props) => {
    const [transform, setTransform] = useState({})

    const onDragStartActive = (ev) => {
        props.onDragStartActive(`item-${props.id}-${props.index}`, props.index, ev, props.id, props.pid)
    }

    const onDragEnterActive = (ev) => {
        props.onDragEnterActive(props.item.title, props.index, ev, props.id, props.pid, `item-${props.id}-${props.index}`)
    }

    useEffect(() => {
        changeTransForm();
    }, [props.changeIndex])

    const changeTransForm = () => {
        if (!props.changeIndex.index && props.changeIndex.index !== 0) { //此时没有要移动的情况出现
            setTransform({
                transform: `translate3d(0px, 0px, 0px)`,
                transitionDuration: "300ms"
            });
            return false;
        }

        //如果是同一个父节点下的从下往上拖拽
        if (
            props.changeIndex.pid === props.moveIndex.pid &&
            props.pid === props.changeIndex.pid &&
            props.index <= props.moveIndex.index &&
            props.index >= props.changeIndex.index
        ) {
            setTransform({
                transform: `translate3d(0px, ${props.initClient.height}px, 0px)`,
                transitionDuration: "300ms"
            });
            return ;
        }

        //如果是同一个父节点下的从上往下拖拽
        if (
            props.changeIndex.pid === props.moveIndex.pid &&
            props.pid === props.changeIndex.pid &&
            props.index >= props.moveIndex.index &&
            props.index <= props.changeIndex.index
        ) {
            setTransform({
                transform: `translate3d(0px, -${props.initClient.height}px, 0px)`,
                transitionDuration: "300ms"
            });
            return ;
        }

        //如果不是同一个父节点且从上往下
        if (
            props.changeIndex.pid !== props.moveIndex.pid &&
            props.enterBody &&
            props.bodyId === props.pid

        ) {
            console.log("进入了父级");
            return ;
        }


        //如果不是同一个父节点且从下往上
        if (
            props.changeIndex.pid !== props.moveIndex.pid &&
            props.enterBody &&
            props.bodyId === props.pid
        ) {
            console.log("进入了父级");
            return ;
        }

        setTransform({
            transform: `translate3d(0px, 0px, 0px)`,
            transitionDuration: "300ms"
        });

    }

    const dragStopActive = {
        onMouseDown: (e) => {
            // e.preventDefault();
            e.stopPropagation();
        },
        onDragStart: (e) => {
            // e.preventDefault();
            e.stopPropagation();
        },
        onDrag: (e) => {
            // e.preventDefault();
            e.stopPropagation();
        },
        onDragEnd: (e) => {
            // e.preventDefault();
            e.stopPropagation();
        }
    }

    const onDragEnter = (ev) => {
        ev.stopPropagation();
        document.getElementById(`list-item-body-${props.id}`).style.paddingBottom = '180px';

        if (props.bodyId === props.id) return ;
        props.enterBody(props.id);
    }

    const onDragLeave = (ev) => {
        document.getElementById(`list-item-body-${props.id}`).style.paddingBottom = '20px';
        ev.stopPropagation()
    }

    return (
        <div
            key={`item-${props.id}`}
            id={`item-${props.id}-${props.index}`}
            style={{margin: '0px auto 20px auto', ...transform}}
            className={'move-active-item'}
            draggable
            onDragStart={onDragStartActive}
            onDrag={props.dragActive}
            onDragEnd={props.dragEndActive}
        >
            <h4 onDragEnter={onDragEnterActive} onClick={() => {console.log(111111)}} >{props.item.title} -- {props.pid} -- {props.index}</h4>
            <div {...dragStopActive} className="desc-ele">{props.item.desc}</div>
            {
                props.item.type === 2 &&
                <div {...dragStopActive} onDragEnter={onDragEnter} onDragLeave={onDragLeave} id={`list-item-body-${props.id}`} className="list-item-body">
                    大body题部分大body题部分大body题部分大body题部分大body题部分大body题部分大body题部分
                    {
                        props.listMap[props.id]?.map((item, index) => (
                            <MoveItem key={item}
                                      item={getItemMsg(item, JSON.parse(JSON.stringify(props.list)))}
                                      id={item}
                                      pid={props.id}
                                      index={index}
                                      changeIndex={props.changeIndex}
                                      initClient={props.initClient}
                                      moveIndex={props.moveIndex}
                                      onDragStartActive={props.onDragStartActive}
                                      dragActive={props.dragActive}
                                      dragEndActive={props.dragEndActive}
                                      onDragEnterActive={props.onDragEnterActive}
                                      enterBody={props.enterBody}
                                      bodyId={props.bodyId}
                                      dragEnterStation={props.dragEnterStation}
                                      list={JSON.parse(JSON.stringify(props.list))}
                                      listMap={JSON.parse(JSON.stringify(props.listMap))}
                            />
                        ))
                    }
                </div>
            }
        </div>
    )
}
let processBoxEle = null;
let processCopiedEle = null;
let initClient = {x: 0, y: 0, height: 0};
let moveIndex = {index: null, id: null,  pid: null};
let initPid = "0";
let bodyEnter = false;
let bodyId = "";
let dragEnterStation = "top"; //top：从上面过来，bottom：从下面过来
let drageData = 0;

const Test = () => {
    const [list, setList] = useState([]);
    // const [list, setList] = useState(["test1", "test2", "test3"]);
    const [listObj, setListObj] = useState({
        list: [],
        relations: {}
    })
    const [changeIndex, setChangeIndex] = useState({index: null, id: null, pid: null});

    useEffect(() => {
        fetch("./list.json").then(response => {
            response.json().then(msg => {
                setListObj(msg)
            }).catch(err => {
                console.error(err)
            })
        }).catch(err => {
            console.error(err)
        })
    }, [])


    const onDragStartActive = (ids, index, ev, id, pid) => {
        processBoxEle = document.getElementById(ids);
        let rectCode = processBoxEle.getBoundingClientRect();
        initClient = {x: rectCode.x - ev.clientX, y: rectCode.y - ev.clientY, height: rectCode.height}
        bodyEnter = false;

        moveIndex = {index: index, id: id, pid: pid};
        setChangeIndex({index: null, id: null, pid: null});
    }

    const dragActive = (ev) => {
        drageData = ev.clientY;
        processBoxEle.style.opacity = "0";
    }

    const dragEndActive = (ev) => {
        processBoxEle.style.opacity = "1";
        afterDrag();
    }

    const onDragEnterActive = (title, index, ev, id, pid, ids) => {
        bodyEnter = false;
        if (changeIndex.index !== index || changeIndex.pid !== pid || changeIndex.id !== id) {
            setChangeIndex({index: index, id: id, pid: pid});
            let enterEle = document.getElementById(ids).getBoundingClientRect();
            if (ev.clientY > enterEle.top) {
                dragEnterStation = "bottom"
            } else {
                dragEnterStation = "top"
            }
            enterEle = null;
        }

    }

    const enterBody = (id) => {
        if (bodyId === id) return ;
        bodyEnter = true;
        bodyId = id;
        console.log("拖拽进入")
        console.log(document.getElementById(`list-item-body-${id}`).getClientRects()[0].top - drageData);
    }

    const afterDrag = () => {
        if ((!changeIndex.index || changeIndex.index === moveIndex.index) && changeIndex.index !== 0 && !bodyEnter) {
            processBoxEle = null;
            moveIndex = {index: null, id: null, pid: null};
            setChangeIndex({index: null, id: null, pid: null});
            return ;
        }

        let relations = {...listObj.relations};
        let list = [...listObj.list];

        relations[moveIndex.pid].splice(moveIndex.index, 1); //不管如何先把初始位置的干掉
        if (bodyEnter && relations[bodyId] !== undefined && dragEnterStation === "top") { //仅是进入新节点的body内
            relations[bodyId].unshift(moveIndex.id);
        } else if (bodyEnter && relations[bodyId] !== undefined && dragEnterStation === "bottom") { //仅是进入新节点的body内
            relations[bodyId].push(moveIndex.id);
        } else if (relations[changeIndex.pid][changeIndex.index] === changeIndex.id) { //证明不是同一个父节点（已经去掉滑动节点之后根据新的位置判断靠谱）
            relations[changeIndex.pid].splice(changeIndex.index, 0, moveIndex.id);
        } else if (moveIndex.index > changeIndex.index) { //往上滑动
            relations[changeIndex.pid].splice(changeIndex.index - 1, 0, moveIndex.id);
        } else { //往下滑动
            relations[changeIndex.pid].splice(changeIndex.index, 0, moveIndex.id);
        }

        setListObj({
            list: list,
            relations: relations
        })


        bodyEnter = false;
        relations = null;
        list = null;
        processBoxEle = null;
        setChangeIndex({index: null, id: null, pid: null});
        moveIndex = {index: null, id: null, pid: null};
    }

    return (
        <div className="App">
            {
                listObj.relations[initPid]?.map((item,index) => (
                    <MoveItem key={item}
                              pid={"0"}
                              index={index}
                              item={getItemMsg(item, [...listObj.list])}
                              id={item}
                              changeIndex={changeIndex}
                              initClient={initClient}
                              moveIndex={moveIndex}
                              onDragStartActive={onDragStartActive}
                              dragActive={dragActive}
                              dragEndActive={dragEndActive}
                              onDragEnterActive={onDragEnterActive}
                              enterBody={enterBody}
                              bodyId={bodyId}
                              dragEnterStation={dragEnterStation}
                              list={JSON.parse(JSON.stringify(listObj.list))}
                              listMap={JSON.parse(JSON.stringify(listObj.relations))}
                    />
                ))
            }
        </div>
    );
}

export default Test;
